import React, { useState } from 'react'

export default function Father() {
  const [person] = useState({
    name: 'Father',
    age: 34
  })
 
  return (
    <div>
      <h1>父组件</h1>

      {/* 通过props.children的方式同时接收Father和Son组件的state(标签体内容会被props通过children属性的方式传递,也可以直接传递children属性) */}
      <Son>{ sonPerson => <GrendSon type='props.children' data={{person, sonPerson}}/> }</Son>

      {/* 通过props.render的方式同时接收Father和Son组件的state(这里的 render属性可以更换为任意属性名，若更换为children，则与上一种方式完全相同) */}
      <Son render={ sonPerson => <GrendSon type='props.render()' data={{person, sonPerson}} />} />

      <Son>
        <GrendSon slot='footer' type='children传多个子结点' data={{person}} />
        普通文本没有props属性
        <span slot='header'>头部</span>
      </Son>
    </div>
  )
}

function Son(props) {
  const [sonPerson] = useState({
    name: 'Son',
    age: 18
  })
  const { map, toArray } = React.Children
  const children = toArray(props.children)
  const headerSlot = children.filter(item => item.props && item.props.slot === 'header')
  const footerSlot = children.filter(item => item.props && item.props.slot === 'footer')
  const defaultSlot = children.filter(item => !item.props || item.props.slot !== 'footer' && item.props.slot !== 'header')
  return (
    <div>
      <h3>子组件</h3>
      {
        // 普通map方法
        // headerSlot.map(item => {
        //   console.log('打印出来的虚拟节点', item);
        //   return item
        // })
        // React.Children提供的map方法
        map(headerSlot, (item => {
          console.log('打印出来的虚拟节点', item);
          return item
        }))
      }
      { defaultSlot }
      {/* props.children就类似于Vue的默认插槽，props.render就类似于Vue具名插槽，同样可写多个 */}
      {/* 如果要将该组件的数据提供给父组件，那么就要使用函数的方式 */}
      { typeof props.children === 'function' && props.children(sonPerson) }
      { typeof props.render === 'function'  && props.render(sonPerson) }
      { footerSlot }
    </div>
  )
}

function GrendSon(props) {
  return (
    <div>
      <span style={{ fontWeight: 'bold' }}>子孙组件(通过{props.type}显示)</span>
      <section>父组件的姓名：{props.data.person.name}, 年龄: {props.data.person.age}</section>
      <section>子组件的姓名：{props.data.sonPerson ? props.data.sonPerson.name : ''}, 年龄: {props.data.sonPerson ? props.data.sonPerson.age : 0}</section>
    </div>
  )
}
